package com.yanyeori.framework.swagger.config;

import com.github.xiaoymin.knife4j.spring.annotations.EnableKnife4j;
import com.yanyeori.framework.swagger.configprop.SwaggerConfigProps;
import lombok.extern.slf4j.Slf4j;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.ResourceHandlerRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
import springfox.documentation.builders.ApiInfoBuilder;
import springfox.documentation.builders.PathSelectors;
import springfox.documentation.builders.RequestHandlerSelectors;
import springfox.documentation.service.ApiInfo;
import springfox.documentation.spi.DocumentationType;
import springfox.documentation.spring.web.plugins.Docket;
import springfox.documentation.swagger2.annotations.EnableSwagger2WebMvc;

/**
 * swagger接口文档自动配置
 *
 * @author chenkuan 2021/1/11
 */
@Slf4j
@Configuration
@ConditionalOnProperty(prefix = "swagger", name = "enabled", havingValue = "true")
@EnableConfigurationProperties({SwaggerConfigProps.class})
@EnableSwagger2WebMvc
@EnableKnife4j
public class SwaggerAutoConfig implements WebMvcConfigurer {
    /*
     * 访问http://ip:port/doc.html
     *
     * @Api：用在controller类，描述API接口
     * @ApiOperation：描述接口方法
     * @ApiModel：描述对象
     * @ApiModelProperty：描述对象属性
     * @ApiImplicitParams：描述接口参数
     * @ApiResponses：描述接口响应
     * @ApiIgnore：忽略接口方法
     */

    /*
     * 访问静态资源(鉴权系统需要允许匿名访问)
     * "/doc.html"              Knife4j提供的文档访问地址
     * "/swagger-resources/**"  Springfox-Swagger提供的分组接口
     * "/webjars/**"
     * "/v3/api-docs"       Knife4j提供的增强接口地址
     */

    @Bean
    public Docket createRestApi(SwaggerConfigProps config) {
        log.debug("Register Knife4j Swagger");
        return new Docket(DocumentationType.SWAGGER_2)
                .enable(config.isEnabled())
                .host(config.getHost())
                .apiInfo(apiInfo(config))
                .select()
                .apis(RequestHandlerSelectors.basePackage(config.getBasePackage()))
                .paths(PathSelectors.any())
                .build();
    }

    private ApiInfo apiInfo(SwaggerConfigProps config) {
        return new ApiInfoBuilder()
                .title(config.getTitle())
                .description(config.getDescription())
                .termsOfServiceUrl(config.getTermsOfServiceUrl())
                .version(config.getVersion())
                .build();
    }

    /**
     * 使用资源处理器注册静态资源
     */
    @Override
    public void addResourceHandlers(ResourceHandlerRegistry registry) {
        registry.addResourceHandler("doc.html").addResourceLocations("classpath:/META-INF/resources/");
        registry.addResourceHandler("/webjars/**").addResourceLocations("classpath:/META-INF/resources/webjars/");
    }
}
